﻿using AnQinFrameWorkAPI.DataBase;
using AnQinFrameWorkAPI.Entity.SystemCore.DTO.RoleField;
using AnQinFrameWorkAPI.Entity.SystemCore.Entity;
using AnQinFrameWorkAPI.Entity.SystemCore.View.RoleField;
using AutoMapper;
using AutoMapper.QueryableExtensions;
using FrameWork.DataHelper;
using FrameWork.Request;
using Microsoft.EntityFrameworkCore;

namespace AnQinFrameWorkAPI.Service.SystemCore;

/// <summary>
///     角色字段业务层
/// </summary>
public class RoleFieldService
{
    #region 获取角色字段列表

    public async Task<RequestResponseModel> GetRoleFieldList(RoleFieldSearchDTO roleFieldSearchDto)
    {
        var roleId = Guid.Parse(roleFieldSearchDto.RoleId);
        var menuId = Guid.Parse(roleFieldSearchDto.MenuId);

        var existingRoleMenuIds = await _context.RoleField
            .Where(rm => rm.RoleId == roleId)
            .Where(a => a.MenuId == menuId)
            .Select(rm => rm.MenuFieldId)
            .ToListAsync();

        var addRoleFieldList = await _context.MenuField
            .Where(m => !existingRoleMenuIds.Contains(m.Id))
            .Select(m => new RoleFieldModel
            {
                Id = Guid.NewGuid(),
                RoleId = roleId,
                MenuId = menuId,
                MenuFieldId = m.Id,
                IsEnable = false
            })
            .ToListAsync();

        if (addRoleFieldList.Count > 0)
        {
            _context.RoleField.AddRange(addRoleFieldList);
            await _context.SaveChangesAsync();
        }

        var query = _context.RoleField
            .ProjectTo<RoleFieldView>(_mapper.ConfigurationProvider)
            .AsQueryable().Where(a => a.RoleId.ToString() == roleFieldSearchDto.RoleId);

        //返回列表
        var roleFieldList = await query
            .Page(roleFieldSearchDto.PageIndex, roleFieldSearchDto.PageSize)
            .ToListAsync();

        //总数据量
        var pageCount = await query.CountAsync();

        //返回数据
        var pageResult = new PageResult<RoleFieldView>(roleFieldList, pageCount);
        return RequestResponse.OK(pageResult, "查询成功");
    }

    #endregion

    #region 启用角色字段

    public async Task<RequestResponseModel> EnableMultiRoleField(RoleFieldUpdateDTO roleFieldUpdateDto)
    {
        //查询角色字段
        var query = await _context.RoleField
            .Where(a => a.RoleId.ToString() == roleFieldUpdateDto.RoleId)
            .Where(a => a.MenuId.ToString() == roleFieldUpdateDto.MenuId)
            .Where(a => roleFieldUpdateDto.FieldId.Contains(a.MenuFieldId.ToString()))
            .ToListAsync();

        if (query.Count != roleFieldUpdateDto.FieldId.Count)
            return RequestResponse.ErrorRequest("角色Id无效或者菜单id无效或者字段列表中有字段ID无效");

        //启用
        foreach (var item in query) item.IsEnable = true;

        _context.RoleField.UpdateRange(query);
        await _context.SaveChangesAsync();
        return RequestResponse.OK(roleFieldUpdateDto.FieldId, "启用成功");
    }

    #endregion

    #region 禁用角色字段

    public async Task<RequestResponseModel> DisableMultiRoleField(RoleFieldUpdateDTO roleFieldUpdateDto)
    {
        //查询角色字段
        var query = await _context.RoleField
            .Where(a => a.RoleId.ToString() == roleFieldUpdateDto.RoleId)
            .Where(a => a.MenuId.ToString() == roleFieldUpdateDto.MenuId)
            .Where(a => roleFieldUpdateDto.FieldId.Contains(a.MenuFieldId.ToString()))
            .ToListAsync();

        if (query.Count != roleFieldUpdateDto.FieldId.Count)
            return RequestResponse.ErrorRequest("角色Id无效或者菜单id无效或者字段列表中有字段ID无效");

        //启用
        foreach (var item in query) item.IsEnable = false;

        _context.RoleField.UpdateRange(query);
        await _context.SaveChangesAsync();
        return RequestResponse.OK(roleFieldUpdateDto.FieldId, "禁用成功");
    }

    #endregion

    #region 初始化

    //数据库
    private readonly DatabaseContext _context;

    //autoMapper
    private readonly IMapper _mapper;

    //构造注入
    public RoleFieldService(DatabaseContext context, IMapper mapper)
    {
        _context = context;
        _mapper = mapper;
    }

    #endregion
}